import {track, trigger} from "./effect";
import {reactive, ReactiveFlags, readonly} from "./reactive";
import {extend, isObject} from "../shared";

export function createGetter(isReadOnly = false, shallow = false) {
    return function get(target, key, receiver) {
        if (key === ReactiveFlags.IS_REACTIVE) {
            return !isReadOnly;
        } else if (key === ReactiveFlags.IS_READONLY) {
            return isReadOnly;
        }

        let res = Reflect.get(target, key, receiver);
        if (shallow) {
            return res;
        }
        //  对于嵌套的处理，如果res是对象类型就再把res包装一边然后return出去。
        if (isObject(res)) {
            return isReadOnly ? readonly(res) : reactive(res);
        }
        if (!isReadOnly) {
            //  依赖收集
            track(target, key)
        }
        return res;
    }
}

export function createSetter() {
    return function set(target: any, key: string | symbol, newValue: any, receiver: any): boolean {
        var res = Reflect.set(target, key, newValue, receiver);
        //  触发依赖收集
        trigger(target, key)
        return res;
    }
}

const get = createGetter();
const set = createSetter()

const readOnlyGet = createGetter(true);
const shallowReadOnlyGet = createGetter(true, true);
export const mutableHandlers = {
    get,
    set
}

export const readonlyHandlers = {
    get: readOnlyGet,
    set(target: any, key: string | symbol, newValue: any, receiver: any): boolean {
        // @ts-ignore
        console.warn(`key ${key} set 失败,因为对象是只读的`, target)
        return true;
    }
}


export const shallowReadonlyHandlers = extend({}, readonlyHandlers, {get: shallowReadOnlyGet})